package git.soulbgm.controller;

import git.soulbgm.common.enums.Status;
import git.soulbgm.common.pojo.PageInfo;
import git.soulbgm.common.pojo.ResultData;
import git.soulbgm.common.pojo.ReturnCode;
import git.soulbgm.pojo.dto.UserDto;
import git.soulbgm.pojo.entity.User;
import git.soulbgm.pojo.vo.UserVo;
import git.soulbgm.security.config.AuthorityConfig;
import git.soulbgm.security.pojo.LoginUser;
import git.soulbgm.service.RoleService;
import git.soulbgm.service.UserService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.web.bind.annotation.*;

import java.util.Arrays;
import java.util.Date;
import java.util.List;

/**
 * 用户管理接口
 *
 * @author SoulBGM
 * @date 2020-09-10 17:14:11
 */
@RequestMapping("user")
@RestController
public class UserController {

    @Autowired
    private UserService userService;

    @Autowired
    private RoleService roleService;

    @Autowired
    private BCryptPasswordEncoder bCryptPasswordEncoder;

    @Autowired
    private AuthorityConfig authorityConfig;

    @GetMapping("findById")
    public ResultData findById(Long id) {
        User user = userService.findById(id);
        if (user != null) {
            UserVo userVo = new UserVo();
            BeanUtils.copyProperties(user, userVo);
            userVo.setRoleIdList(roleService.findByRoleId(user.getId()));
            return ResultData.getResultData(ReturnCode.SUCCESS, userVo);
        }
        return ResultData.getResultData(ReturnCode.INVALID_FAIL);
    }

    @GetMapping("find")
    public ResultData find(UserDto user) {
        PageInfo pageInfo = userService.find(user.getPageNum(), user.getPageSize(), user);
        return ResultData.getResultData(ReturnCode.SUCCESS, pageInfo);
    }

    @PostMapping({"registered", "add"})
    public ResultData registered(@RequestBody UserDto userDto) {
        userDto.setPassword(bCryptPasswordEncoder.encode(userDto.getPassword()));
        User user = new User();
        BeanUtils.copyProperties(userDto, user);
        user.setDelFlag(Status.EXIST.code);
        user.setStatus(Status.NORMAL.code);
        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
        String createUser = user.getUsername();
        if (authentication != null) {
            LoginUser userDetails = (LoginUser) authentication.getPrincipal();
            createUser = userDetails.getUsername();
        }
        user.setCreateUser(createUser);
        user.setUpdateUser(createUser);
        User dbUser = userService.add(user, userDto.getRoleIdList());
        if (dbUser != null) {
            return ResultData.getResultData(ReturnCode.SUCCESS, user);
        } else {
            return ResultData.getResultData(ReturnCode.SAVE_FAIL);
        }
    }

    @PostMapping("update")
    public ResultData update(@RequestBody UserDto userDto) {
        User user = new User();
        userDto.setPassword(null);
        BeanUtils.copyProperties(userDto, user);
        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
        String updateUser = user.getUsername();
        if (authentication != null) {
            LoginUser userDetails = (LoginUser) authentication.getPrincipal();
            updateUser = userDetails.getUsername();
        }
        user.setUpdateUser(updateUser);
        user.setUpdateTime(new Date());

        Boolean result = userService.update(user, userDto.getRoleIdList());
        if (result) {
            return ResultData.getResultData(ReturnCode.SUCCESS);
        } else {
            return ResultData.getResultData(ReturnCode.UPDATE_FAIL);
        }
    }

    @PostMapping("resetPassword")
    public ResultData resetPassword(@RequestBody UserDto userDto) {
        userDto.setNewPassword(authorityConfig.getInitPassword());
        String newPassword = bCryptPasswordEncoder.encode(userDto.getNewPassword());
        User updateUserParam = new User();
        updateUserParam.setId(userDto.getId());
        updateUserParam.setPassword(newPassword);
        Boolean result = userService.update(updateUserParam, null);
        if (result) {
            return ResultData.getResultData(ReturnCode.SUCCESS);
        } else {
            return ResultData.getResultData(ReturnCode.UPDATE_FAIL);
        }
    }

    @PostMapping("changePassword")
    public ResultData changePassword(@RequestBody UserDto userDto) {
        User user = userService.findById(userDto.getId());
        if (!bCryptPasswordEncoder.matches(userDto.getPassword(), user.getPassword())) {
            return ResultData.getResultData(401, "原密码错误");
        }
        user.setPassword(bCryptPasswordEncoder.encode(userDto.getNewPassword()));
        Boolean result = userService.update(user, null);
        if (result) {
            return ResultData.getResultData(ReturnCode.SUCCESS);
        } else {
            return ResultData.getResultData(ReturnCode.UPDATE_FAIL);
        }
    }

    @PostMapping("delete")
    public ResultData delete(String ids) {
        String[] split = ids.split(",");
        List<String> idList = Arrays.asList(split);
        Boolean result = userService.delete(idList);
        if (result) {
            return ResultData.getResultData(ReturnCode.SUCCESS);
        } else {
            return ResultData.getResultData(ReturnCode.REMOVE_FAIL);
        }
    }

}
